# coding=utf-8

import sys, datetime
import  wx
import  wx.lib.mixins.listctrl  as  listmix

from wx.lib.embeddedimage import PyEmbeddedImage
import wx.lib.agw.ultimatelistctrl as ULC

LIST_AUTOSIZE_FILL = -3

SmallUpArrow = PyEmbeddedImage(
    "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAABHNCSVQICAgIfAhkiAAAADxJ"
    "REFUOI1jZGRiZqAEMFGke2gY8P/f3/9kGwDTjM8QnAaga8JlCG3CAJdt2MQxDCAUaOjyjKMp"
    "cRAYAABS2CPsss3BWQAAAABJRU5ErkJggg==")

#----------------------------------------------------------------------
SmallDnArrow = PyEmbeddedImage(
    "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAABHNCSVQICAgIfAhkiAAAAEhJ"
    "REFUOI1jZGRiZqAEMFGke9QABgYGBgYWdIH///7+J6SJkYmZEacLkCUJacZqAD5DsInTLhDR"
    "bcPlKrwugGnCFy6Mo3mBAQChDgRlP4RC7wAAAABJRU5ErkJggg==")

class ListCtrl(wx.ListCtrl, listmix.ListCtrlAutoWidthMixin):
    def __init__(self, parent, ID, pos=wx.DefaultPosition,
                 size=wx.DefaultSize, style=0):
        wx.ListCtrl.__init__(self, parent, ID, pos, size, style)
        listmix.ListCtrlAutoWidthMixin.__init__(self)


class ListCtrlPanel(wx.Panel, listmix.ColumnSorterMixin):
    def __init__(self, parent, log):
        wx.Panel.__init__(self, parent, -1, style=wx.WANTS_CHARS)

        self.parent = parent
        self.log = log
        tID = wx.NewId()
        
        sizer = wx.BoxSizer(wx.VERTICAL)
        
        self.il = ULC.PyImageList(16, 16)

        self.sm_up = self.il.Add(SmallUpArrow.GetBitmap())
        self.sm_dn = self.il.Add(SmallDnArrow.GetBitmap())

        self.list = ULC.UltimateListCtrl(self, wx.ID_ANY, 
            agwStyle=wx.LC_REPORT | wx.LC_VRULES | wx.LC_HRULES | wx.LC_SINGLE_SEL | wx.LC_SORT_ASCENDING | wx.BORDER_NONE 
        )
        
        self.list.SetImageList(self.il, wx.IMAGE_LIST_SMALL)
        sizer.Add(self.list, 1, wx.EXPAND)

        self.PopulateList()

        self.itemDataMap = {}
        self.gameMap = {}
        
        listmix.ColumnSorterMixin.__init__(self, 4)
        #self.SortListItems(0, True)

        self.SetSizer(sizer)
        self.SetAutoLayout(True)

        self.Bind(wx.EVT_LIST_ITEM_SELECTED, self.OnItemSelected, self.list)
        self.Bind(wx.EVT_LIST_ITEM_DESELECTED, self.OnItemDeselected, self.list)
        self.Bind(wx.EVT_LIST_ITEM_ACTIVATED, self.OnItemActivated, self.list)
        self.Bind(wx.EVT_LIST_DELETE_ITEM, self.OnItemDelete, self.list)
        self.Bind(wx.EVT_LIST_COL_CLICK, self.OnColClick, self.list)
        self.Bind(wx.EVT_LIST_COL_RIGHT_CLICK, self.OnColRightClick, self.list)
        self.Bind(wx.EVT_LIST_COL_BEGIN_DRAG, self.OnColBeginDrag, self.list)
        self.Bind(wx.EVT_LIST_COL_DRAGGING, self.OnColDragging, self.list)
        self.Bind(wx.EVT_LIST_COL_END_DRAG, self.OnColEndDrag, self.list)
        self.Bind(wx.EVT_LIST_BEGIN_LABEL_EDIT, self.OnBeginEdit, self.list)

        self.list.Bind(wx.EVT_LEFT_DCLICK, self.OnDoubleClick)
        self.list.Bind(wx.EVT_RIGHT_DOWN, self.OnRightDown)

        # for wxMSW
        self.list.Bind(wx.EVT_COMMAND_RIGHT_CLICK, self.OnRightClick)

        # for wxGTK
        self.list.Bind(wx.EVT_RIGHT_UP, self.OnRightClick)

    def insertItem(self, data, timeString):
        ID, name, slots, count, timestamp = data
        cIndex = self.list.FindItemData(-1, ID)
        new = cIndex < 0
        
        #if new:
        #    try:
        #        index = self.list.InsertStringItem(sys.maxint, name)
        #    except UnicodeDecodeError:
        #        return False
        #else:
        #    index = cIndex
        if not new:
            self.removeItem(ID)
        
        try:
            index = self.list.InsertStringItem(sys.maxint, name)
        except UnicodeDecodeError:
            return False
        
        self.list.SetStringItem(index, 1, str(slots))
        self.list.SetStringItem(index, 2, str(count))
        self.list.SetStringItem(index, 3, timeString)
        self.list.SetItemData(index, ID)
        self.itemDataMap[ID] = (name.lower(), slots, count, timestamp)
        self.gameMap[name.lower()] = ID
        
        #if not new:
        #    self.list.RefreshItem(index)
        return True
        
    def removeItem(self, ID):
        item = self.list.FindItemData(-1, ID)
        if item > -1:
            self.list.DeleteItem(item)
            lname, slots, count, timestamp = self.itemDataMap[ID]
            del(self.itemDataMap[ID])
            del(self.gameMap[lname])
            return True
        return False
        
    def findItemByName(self, name):
        return self.gameMap.get(name, None)

    def PopulateList(self):
        self.list.InsertColumn(0, "Name")
        self.list.InsertColumn(1, "Slots")
        self.list.InsertColumn(2, "Times seen")
        self.list.InsertColumn(3, "Last Announce")
    
        self.list.SetColumnWidth(0, 250)
        self.list.SetColumnWidth(1, 100)
        self.list.SetColumnWidth(2, 100)
        self.list.SetColumnWidth(3, LIST_AUTOSIZE_FILL)

        
    # Used by the ColumnSorterMixin, see wx/lib/mixins/listctrl.py
    def GetListCtrl(self):
        return self.list

    # Used by the ColumnSorterMixin, see wx/lib/mixins/listctrl.py
    def GetSortImages(self):
        return (self.sm_dn, self.sm_up)


    def OnRightDown(self, event):
        x = event.GetX()
        y = event.GetY()
        self.log.WriteText("x, y = %s\n" % str((x, y)))
        item, flags = self.list.HitTest((x, y))

        if item != wx.NOT_FOUND and flags & wx.LIST_HITTEST_ONITEM:
            self.list.Select(item)

        event.Skip()


    def getColumnText(self, index, col):
        item = self.list.GetItem(index, col)
        return item.GetText()


    def OnItemSelected(self, event):
        ##print event.GetItem().GetTextColour()
        self.currentItem = event.m_itemIndex
        #self.log.WriteText("OnItemSelected: %s, %s, %s, %s\n" %
        #                   (self.currentItem,
        #                    self.list.GetItemText(self.currentItem),
        #                    self.getColumnText(self.currentItem, 1),
        #                    self.getColumnText(self.currentItem, 2)))
        #game = self.getColumnText(self.currentItem, 1)
        game = self.list.GetItemText(self.currentItem)
        clipdata = wx.TextDataObject()
        clipdata.SetText(game)
        wx.TheClipboard.Open()
        wx.TheClipboard.SetData(clipdata)
        wx.TheClipboard.Close()
        try:
            #self.log.WriteText(u"\nCopied gamename to clipboard: %s" % game)
            print u"Copied gamename to clipboard: %s" % game
        except UnicodeDecodeError:
            pass
    
        #if self.currentItem == 10:
        #    self.log.WriteText("OnItemSelected: Veto'd selection\n")
        #    #event.Veto()  # doesn't work
        #    # this does
        #    self.list.SetItemState(10, 0, wx.LIST_STATE_SELECTED)

        event.Skip()


    def OnItemDeselected(self, evt):
        return
        item = evt.GetItem()
        self.log.WriteText("OnItemDeselected: %d" % evt.m_itemIndex)

        # Show how to reselect something we don't want deselected
        if evt.m_itemIndex == 11:
            wx.CallAfter(self.list.SetItemState, 11, wx.LIST_STATE_SELECTED, wx.LIST_STATE_SELECTED)


    def OnItemActivated(self, event):
        return
        self.currentItem = event.m_itemIndex
        self.log.WriteText("OnItemActivated: %s\nTopItem: %s" %
                           (self.list.GetItemText(self.currentItem), self.list.GetTopItem()))

    def OnBeginEdit(self, event):
        return
        self.log.WriteText("OnBeginEdit")
        event.Allow()

    def OnItemDelete(self, event):
        return
        self.log.WriteText("OnItemDelete\n")

    def OnColClick(self, event):
        return
        self.log.WriteText("OnColClick: %d\n" % event.GetColumn())
        event.Skip()

    def OnColRightClick(self, event):
        return
        item = self.list.GetColumn(event.GetColumn())
        self.log.WriteText("OnColRightClick: %d %s\n" %
                           (event.GetColumn(), (item.GetText(), item.GetAlign(),
                                                item.GetWidth(), item.GetImage())))

    def OnColBeginDrag(self, event):
        return
        self.log.WriteText("OnColBeginDrag\n")
        ## Show how to not allow a column to be resized
        #if event.GetColumn() == 0:
        #    event.Veto()


    def OnColDragging(self, event):
        return
        self.log.WriteText("OnColDragging\n")

    def OnColEndDrag(self, event):
        return
        self.log.WriteText("OnColEndDrag\n")

    def OnDoubleClick(self, event):
        return
        self.log.WriteText("OnDoubleClick item %s\n" % self.list.GetItemText(self.currentItem))
        event.Skip()

    def OnRightClick(self, event):
        return
        self.log.WriteText("OnRightClick %s\n" % self.list.GetItemText(self.currentItem))
